﻿#include "threadserver.h"
#define ASMORDERDBSTR ConnectPoolFactory::getInstance()->getConnectPool(ConnectPoolFactory::AsmOrderDataBase)

threadServer::threadServer(QObject *parent) : QObject(parent)
{
    threadTimer = new QTimer(this);
    connect(threadTimer,&QTimer::timeout,this,&threadServer::threadServerTimer);
    threadTimer->start(300);
}

//数据库操作定时器
void threadServer::threadServerTimer()
{
    QElapsedTimer timer;timer.start();
    if(!Servercountbool){return;}
    Servercountbool=false;
    /************* 基础信息部分  ServerInitItem***********/
    if(!ServerInitbool){

        if(ServerInitItem.sapPathMap.isEmpty()){
            setSapPathMap();            //读取数据库的路径配置信息
            qDebug()<<"ServerInitItem.sapPathMap.size():"<<ServerInitItem.sapPathMap.size();
        }if(ServerInitItem.UserInfoList.isEmpty()){
            UserInfoListInit();         //获取登录用户信息
            qDebug()<<"ServerInitItem.UserInfoList.size():"<<ServerInitItem.UserInfoList.size();
        }if(ServerInitItem.errorTypeMap.isEmpty()){
            errorTypeMapInit();         //任务状态的错误码与译文
            qDebug()<<"ServerInitItem.errorTypeMap.size():"<<ServerInitItem.errorTypeMap.size();
        }if(ServerInitItem.taskStatusMap.isEmpty()){
            taskStatusMapInit();        //任务状态的错误码与译文
            qDebug()<<"ServerInitItem.taskStatusMap.size():"<<ServerInitItem.taskStatusMap.size();
        }if(ServerInitItem.StationInfoMap.isEmpty()){
            StationPointMapInit();      //二维码站点与二维码绑定
            qDebug()<<"ServerInitItem.StationPointMap.size():"<<ServerInitItem.StationInfoMap.size()
                   <<ServerInitItem.currentStationMap.size();
        }if(ServerInitItem.BindescPodIdMap.isEmpty()){
            shelfBinInfoMapInit();      //实时获取 Bin 的基础信息
            qDebug()<<"ServerInitItem.BindescPodIdMap.size():"<<ServerInitItem.BindescPodIdMap.size();
        }

        if(!ServerInitItem.sapPathMap.isEmpty() && !ServerInitItem.UserInfoList.isEmpty()
                && !ServerInitItem.errorTypeMap.isEmpty() && !ServerInitItem.taskStatusMap.isEmpty()
                && !ServerInitItem.StationInfoMap.isEmpty()
                && !ServerInitItem.BindescPodIdMap.isEmpty()){
            ServerInitbool=true;
        }else{

        }

    }

    /************* 基础信息部分  CurrentServerItem***********/
    if(!ServerItembool){
        if(CurrentServerItem.LiftCodeMap.isEmpty()){
            LiftTaskInit();                                                              //获取升降机的任务信息
            qDebug()<<"CurrentServerItem.LiftCodeMap.size():"<<CurrentServerItem.LiftCodeMap.size();
        }if(CurrentServerItem.AGVCurrentTaskMap.isEmpty()){
            AGVTCurrentTask_Init();                                                     //当前AGV运行信息
            qDebug()<<"CurrentServerItem.AGVCurrentTaskMap.size():"<<CurrentServerItem.AGVCurrentTaskMap.size();
        }if(CurrentServerItem.currentSAPExcelInfoTask.isEmpty()){
            CurrentServerItem.currentSAPExcelInfoTask=readSAPExcelInfoTask(taskFnish_not,"select");   //SAP 正在执行或未完成的任务 taskstatus<=4
        }

        if(!CurrentServerItem.LiftCodeMap.isEmpty()
                && !CurrentServerItem.AGVCurrentTaskMap.isEmpty()){
            ServerItembool=true;
        }
    }

    threadServercount++;
    if(ServerInitbool && ServerItembool){
        if(threadServercount%2==1){
            queryServer::getInstance()->setCurrentServerInitItem(CurrentServerItem,ServerInitItem);     //基础信息
        }else{
            ESS_Single::GetInstance()->setCurrentServerItem(CurrentServerItem,ServerInitItem);          //需要实时更信息 链表表 整合
        }
    }

    Servercountbool=true;
    if(threadServercount>3000){threadServercount=0;}
    if(timer.elapsed()>1000){
        qDebug()<<"Server read data cost:"<<timer.elapsed()<<"ms  "<<QDateTime::currentDateTime().toString("hh:mm ss");timer.restart();
    }

}

//获取AGV任务信息表
QMap<int, SAPExcelInfo> threadServer::readSAPExcelInfoTask(int taskstatus, QString taskType)
{
    QMap<int, SAPExcelInfo> SAPExcelInfoTask;
    QDateTime QDateTimeS=QDateTime::fromString(QDateTime::currentDateTime().toString("yyyy-MM-dd")+" 00:00:00" ,"yyyy-MM-dd hh:mm:ss");
    QDateTime QDateTimeE=QDateTime::fromString(QDateTime::currentDateTime().toString("yyyy-MM-dd")+" 23:59:00" ,"yyyy-MM-dd hh:mm:ss");
//    QDateTimeS=QDateTimeS.addDays(-2);

    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    sqlQuery.setForwardOnly(true);

    //"where pickStation =:pickStation and ((orderId =:orderId and missionId =:missionId) and (status =:status and taskType =:taskType));"
    sqlQuery.prepare("select * from sapExcelinfo "
                     "where (creatTimer >=:creatTimer or finishTimer >=:finishTimer);");
    sqlQuery.addBindValue(QDateTimeS);
    sqlQuery.addBindValue(QDateTimeE);

    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            SAPExcelInfo SAPExcelInfoI;
            SAPExcelInfoI.SAPTaskIndex=sqlQuery.value("SAPTaskIndex").toInt();          //索引 唯一值
            if(SAPExcelInfoTask.contains(SAPExcelInfoI.SAPTaskIndex) || sqlQuery.value("taskStatus").toInt() >= 100){
                continue;
            }

            SAPExcelInfoI.taskType=sqlQuery.value("taskType").toString();               //任务类型  OUT-出库  IN-入库  MOVE-移库  Empty-返空箱
            SAPExcelInfoI.taskTypeDesc=sqlQuery.value("taskTypeDesc").toString();

            SAPExcelInfoI.taskId=sqlQuery.value("taskId").toString();                   //任务编码 唯一性
            SAPExcelInfoI.taskId_ess=sqlQuery.value("taskId_ess").toString();           //夹抱机器人 任务编码 唯一性
            SAPExcelInfoI.taskId_agv=sqlQuery.value("taskId_agv").toString();           //举升机器人 任务编码 唯一性
            SAPExcelInfoI.agvNum=sqlQuery.value("agvNum").toString();                 //楼层走向  2F-3F 3F-2F

            SAPExcelInfoI.taskStatus=sqlQuery.value("taskStatus").toInt();              //任务状态
            SAPExcelInfoI.latstaskStatus=SAPExcelInfoI.taskStatus;                      //上一个任务状态   当前状态与上一状态不一致时更新数据库
            SAPExcelInfoI.taskStatusDesc=sqlQuery.value("taskStatusDesc").toString();   //任务状态注释

            SAPExcelInfoI.cancelTask=sqlQuery.value("cancelTask").toInt();              //大于0  取消
            SAPExcelInfoI.Priority=sqlQuery.value("Priority").toInt();               //出库任务 优先级 1-100 由高到低  默认值不变100
            SAPExcelInfoI.CarCode=sqlQuery.value("CarCode").toInt();                    //车编码
            SAPExcelInfoI.CarStauts=sqlQuery.value("CarStauts").toInt();                //车状态(0未知  1满车架   2空车架)        上料位和下料位由捷思特提供信息，其它位置由AGV自行决定。

            SAPExcelInfoI.taskError=sqlQuery.value("taskError").toInt();                //任务错误代码
            SAPExcelInfoI.errortextEdit=sqlQuery.value("errortextEdit").toString();     //异常原因详细信息

            SAPExcelInfoI.taskTimer=QDateTime::currentDateTime();
            SAPExcelInfoI.creatTimer=sqlQuery.value("creatTimer").toDateTime();         //创建时间
            SAPExcelInfoI.finishTimer=sqlQuery.value("finishTimer").toDateTime();       //完成时间

        /********************* MES 的订单物料信息 *********************/
            SAPExcelInfoI.LabelNo=sqlQuery.value("LabelNo").toString();                         //贴纸凭证号
            SAPExcelInfoI.load=sqlQuery.value("load").toString();                               //装机站点
            SAPExcelInfoI.loadPoint=sqlQuery.value("loadPoint").toInt();                        //装机站点 对应 AGV站点
            SAPExcelInfoI.loadWaitNode=sqlQuery.value("loadWaitNode").toString();               //装机站点 等待点
            SAPExcelInfoI.loadWaitNodePoint=sqlQuery.value("loadWaitNodePoint").toInt();        //装机站点 等待点 对应 AGV站点
            SAPExcelInfoI.workStation=sqlQuery.value("workStation").toString();                 //老化工位
            SAPExcelInfoI.workStationPoint=sqlQuery.value("workStationPoint").toInt();          //老化工位 对应 AGV站点
            SAPExcelInfoI.workWaitStationPoint=sqlQuery.value("workWaitStationPoint").toInt();  //老化工位 等待点 对应 AGV站点
            SAPExcelInfoI.unload=sqlQuery.value("unload").toString();                           //下机站点
            SAPExcelInfoI.unloadPoint=sqlQuery.value("unloadPoint").toInt();                    //下机站点 对应 AGV站点
            SAPExcelInfoI.unloadWaitNode=sqlQuery.value("unloadWaitNode").toString();           //下机站点 等待点
            SAPExcelInfoI.unloadWaitNodePoint=sqlQuery.value("unloadWaitNodePoint").toInt();    //下机站点 等待点 对应 AGV站点
            SAPExcelInfoI.finishNode=sqlQuery.value("finishNode").toString();                   //完成返回站点 等待点
            SAPExcelInfoI.finishNodePoint=sqlQuery.value("finishNodePoint").toInt();            //完成返回站点 对应 AGV站点

            if(!SAPExcelInfoTask.contains(SAPExcelInfoI.SAPTaskIndex)){
                SAPExcelInfoTask.insert(SAPExcelInfoI.SAPTaskIndex,SAPExcelInfoI);
                //qDebug()<<"wait119:"<<SAPExcelInfoI.SAPTaskIndex<<SAPExcelInfoI.Material<<SAPExcelInfoI.taskStatus<<SAPExcelInfoI.taskTimer;
            }
            //qDebug()<<missionInfoI.ikey<<missionInfoI.updateQty<<sqlQuery.record();
        }
    }else {
        qDebug()<<"taskType:"<<taskType<<"querySAPExcelInfoTask"<<sqlQuery.record();
    }

    return SAPExcelInfoTask;
}


void threadServer::setSapPathMap()
{

    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    sqlQuery.setForwardOnly(true);
    sqlQuery.prepare("select * from sapPath;");

    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            sapPath sapPathI;
            sapPathI.Id=sqlQuery.value("Id").toInt();
            sapPathI.Path=sqlQuery.value("Path").toString();
            sapPathI.funcation=sqlQuery.value("funcation").toString();
            sapPathI.para1=sqlQuery.value("para1").toString();
            sapPathI.para2=sqlQuery.value("para2").toString();
            sapPathI.para3=sqlQuery.value("para3").toString();

            if(sapPathI.funcation!="" && sapPathI.Id<100){
                QString path=sapPathI.funcation+"?";
                if(sapPathI.para1!=""){
                     path=path+sapPathI.para1+"=";
                    if(sapPathI.para2!=""){
                         path="&"+path+sapPathI.para2+"=";
                        if(sapPathI.para3!=""){
                             path="&"+path+sapPathI.para3+"=";
                        }
                    }
                }
                sapPathI.Path=sapPathI.Path+path;
            }

            sapPathI.Type=sqlQuery.value("Type").toString();        //路径类型 发料时根据类型 选择路径
            sapPathI.PathName=sqlQuery.value("PathName").toString();
            ServerInitItem.sapPathMap.insert(sapPathI.Id,sapPathI);
        }
    }

}

void threadServer::UserInfoListInit()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    QSqlQuery sqlQuery2(sqlDatabase);

    sqlQuery2.setForwardOnly(true);
    ServerInitItem.UserInfoList.clear();
    sqlQuery2.prepare("select * from userinfo;");
    if(sqlQuery2.exec())
    {
        while(sqlQuery2.next())
        {
            User_Info UserInfoItiem;
            UserInfoItiem. UserNuber=sqlQuery2.value("UserNuber").toString();      //编号
            UserInfoItiem. UserName=sqlQuery2.value("UserName").toString();       //姓名
            UserInfoItiem. PassWord=sqlQuery2.value("PassWord").toString();       //密码
            UserInfoItiem. Jurisdiction=sqlQuery2.value("Jurisdiction").toString();   //权限
            UserInfoItiem. UserGrage=sqlQuery2.value("UserGrage").toString();      // 等级
            UserInfoItiem. Status=sqlQuery2.value("Status").toString();        //编辑状态 -1删除
            ServerInitItem.UserInfoList.append(UserInfoItiem);
            //qDebug()<<UserInfoItiem. UserNuber<<UserInfoItiem. UserName<<UserInfoItiem. PassWord;
        }
    }

}

//AGV任务动作
void threadServer::AGVTCurrentTask_Init()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);

    sqlQuery.setForwardOnly(true);
    sqlQuery.prepare("select * from AGVCurrentTask ;");
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            AGVCurrentTask AGVCurrentTaskI;
            AGVCurrentTaskI.AGVId=sqlQuery.value("AGVId").toInt();                      //小车编号
            AGVCurrentTaskI.AGVIP=sqlQuery.value("AGVIP").toString();                   //小车 ip
            AGVCurrentTaskI.enable=sqlQuery.value("enable").toInt();                    //1使用  0禁用
            AGVCurrentTaskI.AGVType=sqlQuery.value("AGVType").toInt();                  //AGV类型    0默认小精灵   1夹抱AGV
            AGVCurrentTaskI.floornum=sqlQuery.value("floornum").toInt();                //AGV所在楼层
            AGVCurrentTaskI.waitPoint=sqlQuery.value("waitPoint").toInt();              //待机点二维码

            AGVCurrentTaskI.taskId=sqlQuery.value("taskId").toString();                    //唯一识别号
            AGVCurrentTaskI.lastTaskId=sqlQuery.value("lastTaskId").toString();            //上一个任务--唯一识别号
            AGVCurrentTaskI.taskType=sqlQuery.value("taskType").toInt();                //任务类型 IN入库  OUT出库
            AGVCurrentTaskI.SAPTaskIndex=sqlQuery.value("SAPTaskIndex").toInt();           //任务索引 唯一值

            AGVCurrentTaskI.JOBState=sqlQuery.value("JOBState").toInt();                   //任务状态
            AGVCurrentTaskI.AGVState=sqlQuery.value("AGVState").toInt();                   //AGV 状态 0：正在运行，1：空闲， 2：异常，3：正在充电
            AGVCurrentTaskI.errorCode=sqlQuery.value("errorCode").toInt();                 //故障代码（故障代码参考表）
            AGVCurrentTaskI.alarmCode=sqlQuery.value("alarmCode").toInt();                 //警告代码（警告代码参考表）
            AGVCurrentTaskI.batteryLevel=sqlQuery.value("batteryLevel").toInt();           //AGV 电量，百分比
            AGVCurrentTaskI.currentNode=sqlQuery.value("agvStation").toInt();              //AGV运行时的节点
            AGVCurrentTaskI.currentStation=sqlQuery.value("currentStation").toInt();    //AGV当前执行的任务站点，未执行任务为空
            AGVCurrentTaskI.agvPosition=sqlQuery.value("agvPosition").toString();          //AGV位置信息(x,y)---(6090,20310)
            /*********** 任务状态信息 ***********/
            AGVCurrentTaskI.status=sqlQuery.value("status").toInt();                       //任务状态   0:未执行 1:正在运行, 2：已完成
            AGVCurrentTaskI.station=sqlQuery.value("station").toString();                  //动作站点
            AGVCurrentTaskI.action=sqlQuery.value("action").toInt();                       //0:装载（取货）1:卸载（送货）
            AGVCurrentTaskI.msg=sqlQuery.value("msg").toString();                          //任务反馈描述

            if(!CurrentServerItem.AGVCurrentTaskMap.contains(QString::number(AGVCurrentTaskI.AGVId))
                    && AGVCurrentTaskI.enable==1){
                CurrentServerItem.AGVCurrentTaskMap.insert(QString::number(AGVCurrentTaskI.AGVId),AGVCurrentTaskI);
                ServerInitItem.AGVIPInitMap.insert(QString::number(AGVCurrentTaskI.AGVId),AGVCurrentTaskI.waitPoint);              //AGVIP 与 待机点
                //qDebug()<<"AGVIP:"<<AGVCurrentTaskI.AGVIP<<" AGVType:"<<AGVCurrentTaskI.AGVType<<" chargeIP:"<<AGVCurrentTaskI.chargeIP;
            }

        }
    }

}

void threadServer::LiftTaskInit()
{

    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);

    sqlQuery.setForwardOnly(true);
    sqlQuery.prepare("select * from LiftTask ;");
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            LiftCode LiftCodeI;
            LiftCodeI.codeDesc=sqlQuery.value("codeDesc").toString();           //升降机接驳台命名 2F-IN
            LiftCodeI.Liftstatus=sqlQuery.value("Liftstatus").toInt();          //升降机感应器状态 (IN-D100 D103 D105:1可放料,2-3去X楼) (OUT-D101 D102 D104: 1可取料,2取料完成)
            LiftCodeI.codeType=sqlQuery.value("codeType").toString();           //(IN- D100 D103 D105:1可放料,2-3去X楼)  ( OUT- D101 D102 D104: 1可取料,2取料完成)
            LiftCodeI.status=sqlQuery.value("status").toInt();                  //任务锁定状态:0空闲  1 锁定  2到达 0空闲
            LiftCodeI.SAPTaskIndex=sqlQuery.value("SAPTaskIndex").toInt();      //任务索引 唯一值
            LiftCodeI.containerCode=sqlQuery.value("containerCode").toString(); //容器编码 (即胶箱编码) ->唯一
            if(!CurrentServerItem.LiftCodeMap.contains(LiftCodeI.codeDesc)){
                CurrentServerItem.LiftCodeMap.insert(LiftCodeI.codeDesc,LiftCodeI);
//                qDebug()<<"codeDesc:"<<LiftCodeI.codeDesc<<" status:"<<LiftCodeI.status
//                       <<" SAPTaskIndex:"<<LiftCodeI.SAPTaskIndex<<" containerCode:"<<LiftCodeI.containerCode;
            }
        }
    }
}

//任务状态的错误码与译文
void threadServer::taskStatusMapInit()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    sqlQuery.setForwardOnly(true);
    ServerInitItem.taskStatusMap.clear();
    sqlQuery.prepare("select * from StatusMap;");
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            ServerInitItem.taskStatusMap.insert(sqlQuery.value("statusId").toString(),sqlQuery.value("taskStatus").toString());
        }
    }

}

void threadServer::errorTypeMapInit()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    sqlQuery.setForwardOnly(true);
    ServerInitItem.errorTypeMap.clear();
    sqlQuery.prepare("select * from errorType;");//操作时 错误类型 错误码与译文
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            ServerInitItem.errorTypeMap.insert(sqlQuery.value("errorTypeId").toInt(),sqlQuery.value("errorTypeDesc").toString());
        }
    }
}

void threadServer::StationPointMapInit()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);

    sqlQuery.setForwardOnly(true);
    sqlQuery.prepare("select * from deviceI where  enable =:enable;");
    sqlQuery.addBindValue(1);
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            deviceI deviceItem;
            /******************* 接驳台类型 **************/
            deviceItem.deviceId=sqlQuery.value("deviceId").toInt();                 //设备Id
            deviceItem.deviceIP=sqlQuery.value("deviceIP").toString();              //设备IP
            deviceItem.deviceDesc=sqlQuery.value("deviceDesc").toString();          //设备名称
            deviceItem.deviceType=sqlQuery.value("deviceType").toString();          //设备类型
            deviceItem.enable=sqlQuery.value("enable").toInt();                     //使能
            deviceItem.floor=sqlQuery.value("floor").toInt();                       //优先级

            /******************* 接驳台类型 **************/
            deviceItem.stationStatus=sqlQuery.value("stationStatus").toInt();       //站点类型
            deviceItem.StationType=sqlQuery.value("StationType").toString();        //站点类型
            deviceItem.stationDesc=sqlQuery.value("stationDesc").toString();        //站点名称
            deviceItem.Currentpoint=sqlQuery.value("Currentpoint").toInt();         //当前所在节点
            deviceItem.currentStation=sqlQuery.value("currentStation").toInt();     //当前所在站点
            deviceItem.waitDesc=sqlQuery.value("waitDesc").toString();              //待机点二维码
            deviceItem.waitPoint=sqlQuery.value("waitPoint").toInt();               //当前所在二维码
            deviceItem.scanCode=sqlQuery.value("scanCode").toString();              //工单条码

            ServerInitItem.StationInfoMap.insert(deviceItem.deviceDesc,deviceItem);
            ServerInitItem.StationDesMap.insert(deviceItem.stationDesc,deviceItem.deviceDesc);
            ServerInitItem.StationDesMap_.insert(deviceItem.deviceDesc,deviceItem.stationDesc);
            ServerInitItem.currentStationMap.insert(deviceItem.currentStation,deviceItem.Currentpoint);

        }
    }

}

void threadServer::shelfBinInfoMapInit()
{
    connectBuilder build(ASMORDERDBSTR);
    QSqlDatabase sqlDatabase =  build.getOpenDatabase();
    QSqlQuery sqlQuery(sqlDatabase);
    sqlQuery.setForwardOnly(true);
    sqlQuery.prepare("select * from shelfInfo ;");
    if(sqlQuery.exec())
    {
        while(sqlQuery.next())
        {
            shelfBinInfo shelfBinInfoI;
            shelfBinInfoI.shelfBinIndex=sqlQuery.value("shelfBinIndex").toInt();        //所属架位索引
            shelfBinInfoI.shelfBindesc=sqlQuery.value("shelfBindesc").toString();       //所属架位注释
            shelfBinInfoI.podIdDesc=sqlQuery.value("podIdDesc").toString();             //货架注释
            ServerInitItem.BindescPodIdMap.insert(shelfBinInfoI.podIdDesc,shelfBinInfoI.shelfBindesc);
        }
    }

}
